const User = require('../models/userModel');
const jwt = require('jsonwebtoken');
const { verifyCaptcha, generateCaptcha } = require('./captchaController');
const Response = require('../utils/response');
const Role = require('../models/roles');
const RoleMenu = require('../models/roles_menus');
const Menu = require('../models/menus');

class UserController {
  // 用户登录
  async login(ctx) {
    try {
      const { username, password, captcha } = ctx.request.body;

      // 验证输入
      if (!username || !password || !captcha) {
        ctx.status = 400;
        ctx.body = Response.error('请提供用户名、密码和验证码', 400);
        return;
      }

      // 验证验证码
      if (!verifyCaptcha(captcha, ctx.session)) {
        ctx.status = 400;
        ctx.body = Response.error('验证码错误', 400);
        return;
      }

      // 查找用户
      const user = await User.findOne({ username }).select('+password');
      if (!user) {
        ctx.status = 401;
        ctx.body = Response.error('用户名或密码错误', 401);
        return;
      }

      // 验证密码
      const isMatch = await user.comparePassword(password);
      if (!isMatch) {
        ctx.status = 401;
        ctx.body = Response.error('用户名或密码错误', 401);
        return;
      }

      // 生成 token
      const token = jwt.sign(
        {
          id: user.id,
          username: user.username,
          role: user.role
        },
        process.env.JWT_SECRET,
        { expiresIn: '24h' }
      );

      console.log('Login user id:', user.id);

      // 只返回token
      ctx.body = Response.success({
        token
      }, '登录成功');

    } catch (error) {
      console.error('登录失败:', error);
      ctx.status = 500;
      ctx.body = Response.error('登录失败：' + error.message);
    }
  }

  // 用户注册
  async register(ctx) {
    try {
      const { username, password, captcha, nickName, introduction, avatar } = ctx.request.body;

      // 验证必填字段
      if (!username || !password || !captcha) {
        ctx.status = 400;
        ctx.body = Response.error('用户名、密码、名称和验证码都是必需的', 400);
        return;
      }

      // 验证验证码
      if (!ctx.session.captcha ||
        captcha.toLowerCase() !== ctx.session.captcha) {
        ctx.status = 400;
        ctx.body = Response.error('验证码错误', 400);
        return;
      }

      // 清除已使用的验证码
      delete ctx.session.captcha;

      // 检查是否已存在
      const existingUser = await User.findOne({ username });
      if (existingUser) {
        ctx.status = 400;
        ctx.body = Response.error('用户名已存在', 400);
        return;
      }

      // 创建新用户
      const user = await User.create({
        username,
        password,
        nickName,
        state: true,
        introduction,
        avatar,
        role: 'user'
      });

      // 生成 token
      const token = jwt.sign(
        { id: user._id, username: user.username },
        process.env.JWT_SECRET,
        { expiresIn: '24h' }
      );

      // 不返回密码
      const userWithoutPassword = user.toObject();
      delete userWithoutPassword.password;

      ctx.status = 201;
      ctx.body = Response.success({
        token,
        user: userWithoutPassword
      }, '注册成功');
    } catch (error) {
      console.error('注册失败:', error);
      ctx.status = 500;
      ctx.body = Response.error('注册失败：' + error.message);
    }
  }

  // 获取验证码
  async getCaptcha(ctx) {
    try {
      await generateCaptcha(ctx);
    } catch (error) {
      console.error('生成验证码失败:', error);
      ctx.status = 500;
      ctx.body = Response.error('生成验证码失败');
    }
  }

  // 获取用户列表
  async getUsers(ctx) {
    try {
      const { page = 1, limit = 10, username = '' } = ctx.query;
      const skip = (page - 1) * limit;

      // 构建查询条件
      const query = {};
      if (username) {
        query.$or = [
          { username: { $regex: username, $options: 'i' } },
          { nickName: { $regex: username, $options: 'i' } }
        ];
      }

      // 获取总数
      const total = await User.countDocuments(query);

      // 获取分页数据
      const users = await User.find(query)
        .select('-password') // 排除密码字段
        .skip(skip)
        .limit(Number(limit))
        .sort({ createdAt: -1 });

      ctx.body = Response.success({
        total,
        page: Number(page),
        limit: Number(limit),
        data: users
      });
    } catch (error) {
      ctx.status = 500;
      ctx.body = Response.error(error.message);
    }
  }

  // 获取单个用户
  async getUserById(ctx) {
    try {
      const user = await User.findOne({ id: ctx.params.id });
      if (!user) {
        ctx.status = 404;
        ctx.body = Response.error('用户不存在', 404);
        return;
      }
      ctx.body = Response.success(user);
    } catch (error) {
      ctx.status = 500;
      ctx.body = Response.error(error.message);
    }
  }

  // 更新用户
  async updateUser(ctx) {
    try {
      const user = await User.findOneAndUpdate(
        { id: ctx.params.id },
        ctx.request.body,
        { new: true, runValidators: true }
      );
      if (!user) {
        ctx.status = 404;
        ctx.body = Response.error('用户不存在', 404);
        return;
      }
      ctx.body = Response.success(user);
    } catch (error) {
      ctx.status = 400;
      ctx.body = Response.error(error.message);
    }
  }

  // 删除用户
  async deleteUser(ctx) {
    try {
      const user = await User.findOneAndDelete({ id: ctx.params.id });
      if (!user) {
        ctx.status = 404;
        ctx.body = Response.error('用户不存在', 404);
        return;
      }
      ctx.body = Response.success(null, '删除成功');
    } catch (error) {
      ctx.status = 500;
      ctx.body = Response.error(error.message);
    }
  }

  // 获取当前用户信息和路由
  async getCurrentUser(ctx) {
    try {
      // 从 token 中获取用户 ID
      const userId = ctx.state.user.id;

      // 查找用户信息
      const user = await User.findOne({ id: userId });
      if (!user) {
        ctx.status = 404;
        ctx.body = Response.error('用户不存在', 404);
        return;
      }

      // 获用户角色 - 使用角色的 name 字段查询
      const role = await Role.findOne({ name: user.role });

      if (!role) {
        // 如果找不到角色，返回基本用户信息，但不返回菜单
        ctx.body = Response.success({
          user: {
            id: user.id,
            username: user.username,
            nickName: user.nickName,
            role: user.role,
            avatar: user.avatar,
            introduction: user.introduction
          },
          menus: []  // 返回空菜单列表
        });
        return;
      }

      // 获取角色的菜单权限
      const roleMenus = await RoleMenu.find({ role_id: role.id });
      const menuIds = roleMenus.map(rm => rm.menu_id);

      // 获取所有菜单
      const menus = await Menu.find({
        id: { $in: menuIds }
      });

      // 递归获取按钮权限标识
      const getButtonPermissions = (menuList) => {

        let permissions = [];
        for (const menu of menuList) {
          // 如果是按钮类型且有权限标识
          if (menu.level == 2 && menu.permission) {
            permissions.push(menu.permission);
          }
        }
        return permissions;
      };


      // 获取所有按钮权限
      const permissions = getButtonPermissions(menus);

      // 构建菜单树（过滤掉按钮类型）
      const menuTree = buildMenuTree(menus.filter(menu => menu.level !== 2));

      // 返回用户信息、菜单树和权限列表
      ctx.body = Response.success({
        user: {
          id: user.id,
          username: user.username,
          nickName: user.nickName,
          role: user.role,
          avatar: user.avatar,
          introduction: user.introduction
        },
        menus: menuTree,
        permissions: permissions
      });

    } catch (error) {
      console.error('获取用户信息失败:', error);
      ctx.status = 500;
      ctx.body = Response.error('获取用户信息失败：' + error.message);
    }
  }

  // 更改用户角色
  async updateUserRole(ctx) {
    try {
      const { userId } = ctx.params;
      const { role } = ctx.request.body;

      // 验证角色是否存在
      const existingRole = await Role.findOne({ id: role });
      if (!role || !existingRole) {
        ctx.status = 400;
        ctx.body = Response.error('无效的角色ID');
        return;
      }

      // 查找用户
      const user = await User.findOne({ id: userId });
      if (!user) {
        ctx.status = 404;
        ctx.body = Response.error('用户不存在');
        return;
      }
      // 更新用户角色
      user.role = existingRole.name; // 使用角色名称而不是ID
      await user.save(); // 使用save方法确保触发中间件
      // 返回更新后的用户信息（不包含密码）
      const updatedUser = user.toObject();
      delete updatedUser.password;
      ctx.body = Response.success(updatedUser, '用户角色更新成功');
    } catch (error) {
      console.error('更新用户角色失败:', error);
      ctx.status = 500;
      ctx.body = Response.error('更新用户角色失败：' + error.message);
    }
  }
  // 添加用户（需要权限）
  async createUser(ctx) {
    try {
      const { username, password, nickName, introduction, avatar, role = 'user' } = ctx.request.body;

      // 验证必填字段
      if (!username || !password) {
        ctx.status = 400;
        ctx.body = Response.error('用户名和密码为必填项', 400);
        return;
      }

      // 检查用户名是否已存在
      const existingUser = await User.findOne({ username });
      if (existingUser) {
        ctx.status = 400;
        ctx.body = Response.error('用户名已存在', 400);
        return;
      }

      // 验证角色是否存在
      const existingRole = await Role.findOne({ name: role });
      if (!existingRole) {
        ctx.status = 400;
        ctx.body = Response.error('无效的角色', 400);
        return;
      }

      // 创建新用户
      const user = await User.create({
        username,
        password,
        nickName: nickName || username,
        role,
        state: true,
        introduction,
        avatar
      });

      // 不返回密码
      const userWithoutPassword = user.toObject();
      delete userWithoutPassword.password;

      ctx.status = 201;
      ctx.body = Response.success(userWithoutPassword, '用户创建成功');
    } catch (error) {
      console.error('创建用户失败:', error);
      ctx.status = 500;
      ctx.body = Response.error('创建用户失败：' + error.message);
    }
  }

  // 编辑用户信息
  async updateUserInfo(ctx) {
    try {
      const userId = ctx.params.id;
      const updateData = ctx.request.body;

      // 验证用户是否存在
      const user = await User.findOne({ id: userId });
      if (!user) {
        ctx.status = 404;
        ctx.body = Response.error('用户不存在');
        return;
      }

      // 如果要修改用户名，检查是否重复
      if (updateData.username && updateData.username !== user.username) {
        const existingUser = await User.findOne({ username: updateData.username });
        if (existingUser) {
          ctx.status = 400;
          ctx.body = Response.error('用户名已存在');
          return;
        }
      }

      // 如果包含密码，需要加密
      if (updateData.password) {
        // 密码会在 model 中自动加密
        user.password = updateData.password;
        await user.save();
        delete updateData.password;  // 从更新数据中移除密码
      }

      // 更新其他信息
      const updatedUser = await User.findOneAndUpdate(
        { id: userId },
        {
          ...updateData,
          updatedAt: new Date()
        },
        { new: true }
      ).select('-password');  // 不返回密码字段

      ctx.body = Response.success(updatedUser, '用户信息更新成功');
    } catch (error) {
      console.error('更新用户信息失败:', error);
      ctx.status = 500;
      ctx.body = Response.error('更新用户信息失败：' + error.message);
    }
  }
}

// 构建菜单树的辅助函数
function buildMenuTree(menus, parentId = '') {
  return menus
    .filter(menu => menu.parent_id === parentId)
    .map(menu => ({
      ...menu.toObject(),
      meta: { title: menu.title, icon: menu.icon, isShow: menu.hidden },
      children: buildMenuTree(menus, menu.id)
    }))
    .sort((a, b) => (a.sort || 0) - (b.sort || 0));
}

module.exports = new UserController(); 